package study08_heartbeat.client;

import io.netty.bootstrap.Bootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import io.netty.util.concurrent.GenericFutureListener;
import io.netty.util.concurrent.ScheduledFuture;
import lombok.extern.slf4j.Slf4j;

import java.util.Random;
import java.util.concurrent.TimeUnit;

/**
 * @author kdyzm
 */
@Slf4j
public class HeartBeatClientHandler extends ChannelInboundHandlerAdapter {

    private GenericFutureListener listener;

    private ScheduledFuture scheduledFuture;

    private Bootstrap bootstrap;

    public HeartBeatClientHandler(Bootstrap bootstrap) {
        this.bootstrap = bootstrap;
    }

    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        //随机发送心跳
        randomSend(ctx.channel());
    }

    //随机发送心跳
    private void randomSend(Channel channel) {
        int heartBeatInterval = new Random().nextInt(7)+1;
        log.info("{}秒之后发送下一次心跳", heartBeatInterval);

        scheduledFuture=channel.eventLoop().schedule(() -> {
            if (channel.isActive()) {
                log.info("开始向服务器发送心跳");
                channel.writeAndFlush("~ping~");
            } else {
                log.info("与服务器的连接已经断开");
            }
        }, heartBeatInterval, TimeUnit.SECONDS);

        //定义监听器
        listener = (future) -> {
            randomSend(channel);
        };
        //为异步定时任务添加监听器
        scheduledFuture.addListener(listener);
    }

    @Override
    public void channelInactive(ChannelHandlerContext ctx) throws Exception {
        //移除监听器
        scheduledFuture.removeListener(listener);

        log.info("即将开始重连");
        //断开之后立马重新连接
        bootstrap.connect("127.0.0.1",8888).sync();
    }

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        log.error("", cause);
        ctx.close();
    }
}
